﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace RPGKata
{
    class Party
    {
        private Dictionary<string,Character> characters;
        private List<Character> order;

        public Party()
        {
            characters = new Dictionary<string, Character>();
            order = new List<Character>();
        }
        
        public void addCharacter(Character c)
        {
            characters.Add(c.getName(), c);
        }

        public void createCharacter()
        {
            Console.WriteLine("Let's create the characters for this party");
            while (Console.ReadLine().ToLower() != "no")
            {
                Console.WriteLine("Name your character");
                Character c = new Character();
                c.setName(Console.ReadLine());
                Console.WriteLine("What's your character's strength?");
                c.setStrength(Console.ReadLine());
                Console.WriteLine("What's your character's constitution?");
                c.setConstitution(Console.ReadLine());
                Console.WriteLine("What's your character's dexterity?");
                c.setDexterity(Console.ReadLine());
                addCharacter(c);
                Console.WriteLine("Want to make another character? yes/no");
            }
        }

        public void createWeapon()
        {
            Console.WriteLine("Let's create the weapons for your characters.");
            while (Console.ReadLine().ToLower() != "no")
            {
                Console.WriteLine("Name your weapon");
                Weapon w = new Weapon();
                w.setName(Console.ReadLine());
                Console.WriteLine("What's the weapon's damage?");
                w.setDamage(Console.ReadLine());
                Console.WriteLine("Write the name of the character you made this weapon for.");
                printCharacterNames();
                assignWeaponToCharacter(w,Console.ReadLine());
                Console.WriteLine("Want to make nore weapons? yes/no");
            }
        }

        public void createArmor()
        {
            Console.WriteLine("Let's create the armor for your characters.");
            while (Console.ReadLine().ToLower() != "no")
            {
                Console.WriteLine("Name your armor");
                Armor a = new Armor();
                a.setName(Console.ReadLine());
                Console.WriteLine("What's the armor's protection?");
                a.setProtection(Console.ReadLine());
                Console.WriteLine("What's the armor's encumbrance?");
                a.setEncumbrance(Console.ReadLine());
                Console.WriteLine("Write the name of the character you made this armor for.");
                printCharacterNames();
                assignArmorToCharacter(a, Console.ReadLine());
                Console.WriteLine("Want to make more armor? yes/no");
            }
        }

        public void assignWeaponToCharacter(Weapon w, string name)
        {
            Character c = findCharacter(name);
            while (c == null)
            {
                Console.WriteLine("Character doesn't exist. Please write in a character's name");
                name = Console.ReadLine();
                c = findCharacter(name);
            }
            while (c != null && c.isArmorEquipped())
            {
                Console.WriteLine("This character already has a weapon. Choose another character. If you want to replace the current weapon, type replace");
                name = Console.ReadLine().ToLower();
                if (name == "replace")
                {
                    c.setWeapon(w);
                }
                c = findCharacter(name);
            }
            c.setWeapon(w);
        }
                
        public void assignArmorToCharacter(Armor a, string name)
        {
            Character c = findCharacter(name);
            while (c == null)
            {
                Console.WriteLine("Character doesn't exist. Please write in a character's name");
                name = Console.ReadLine();
                c = findCharacter(name);
            }
            while (c != null && c.isArmorEquipped())
            {
                Console.WriteLine("This character already has armor. Choose another character. If you want to replace the current armor, type replace");
                name = Console.ReadLine().ToLower();
                if ( name == "replace")
                {
                    c.setArmor(a);
                }
                c = findCharacter(name);
            }
            c.setArmor(a);
        }

        public void printCharacterNames()
        {
            foreach (KeyValuePair<string, Character> kvp in characters)
            {
                Console.WriteLine("Name of Character: {0}", kvp.Key);
            }
        }

        public Character findCharacter(string name)
        {
            Character value;
            if(characters.TryGetValue(name, out value))
            {
                return value;
            }
            else
            {
                return null;
            }
        }

        public void getOrder()
        {
            order.Clear();
            foreach (KeyValuePair<string, Character> kvp in characters)
            {
                kvp.Value.setRollDexterity();
            }

            var orders = from value in characters.Values orderby value.getRollDexterity() ascending select value;

            foreach (Character c in orders)
            {
                order.Add(c);
            }
        }

        public Character getRandomCharacter()
        {
            int index = Roll.randomNumber(0, order.Count);
            return order[index];
        }

        public void turn(Party enemy)
        {
            removeDeadCharacters();
            getOrder();
            foreach (Character c in order)
            {
                c.setOpponent(enemy.getRandomCharacter());
                c.Attack();
            }

        }

        public void removeDeadCharacters()
        {
            for (int index = 0; index < order.Count; index++)
            {
                if (order[index].isDead())
                {
                    Character c = order[index];
                    characters.Remove(c.getName());

                }
            }
        }
    }
}
